﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using SegIdenPC.Entidad;
using SegIdenPC.Herramientas;
using log4net;
using GS1.Utilitario;
using System.Drawing.Imaging;
using System.Configuration;
using SegIdenPC.Utilitarios;
using System.Diagnostics;


namespace SegIdenPC.Formularios
{
    public partial class frmReporteVenta : Form
    {
        #region --- Variables y Propiedades ---
        private static readonly ILog log = LogManager.GetLogger(typeof(frmReporteVenta));

        private const string LLAVE_RUTAIMAGEN = "RUTAARCHIVO";

        private const string TITULO = "Reporte Venta";
        private const string FORMATO_TOTAL_ENCONTRADOS = "Total registros: {0}";

        private string RUTA_ARCHIVO_TEMPORAL = ConfigurationManager.AppSettings[LLAVE_RUTAIMAGEN];
        private const string APLICACION_EXCEL = "excel.exe";

        private const string FORMATO_PRODUCTO_DESCRIPCION_DETALLADA = "{0} - {1} - {2} - {3}";

        private Tienda tiendaReporte = null;
        private Producto productoReporte = null;
        private Cliente clienteReporte = null;
        private Diseniador diseniadorReporte = null;
        private ReporteVenta reporteVenta = null;

        #endregion

        #region --- Constructor ---
        public frmReporteVenta()
        {
            InitializeComponent();
        }
        #endregion

        #region --- Eventos Formulario ---
        private void frmReporteVenta_Load_1(object sender, EventArgs e)
        {cargarFormulario();

        }
        private void btnBuscarTiendaO_Click_1(object sender, EventArgs e)
        {
            elegirTienda();
        }

           private void btnBuscarDecorador_Click_1(object sender, EventArgs e)
        {
            elegirDecorador();
        }
        private void btnBuscarProducto_Click_1(object sender, EventArgs e)
        {
            elegirProducto();
        }
        private void btnBuscarCliente_Click_1(object sender, EventArgs e)
        {
            elegirCliente();
        }

        private void cboTipoDocumento_SelectedIndexChanged(object sender, EventArgs e)
        {
            if (this.cboTipoDocumento.Focused) { limpiarDatosCliente(); }
        }

        private void tbtnImprimir_Click(object sender, EventArgs e)
        {
            exportarData();
        }

        private void tbtnSalir_Click(object sender, EventArgs e)
        {
            salir();
        }
        private void tbtnVer_Click_1(object sender, EventArgs e)
        {
            ejecutarReporte();
        }
     
        #endregion

        #region --- Metodos Propios ---

        private void cargarFormulario()
        {
            ListaGeneral listaReporte = null;
            ListaGeneral listaTipoDocumento = null;


            try
            {
                Cursor.Current = Cursors.WaitCursor;

                // Instanciando y creando listado de estado
                listaReporte = new ListaGeneral();
                listaReporte.Add(new General { codigo = "0", descripcion = "---Seleccione---" });
                listaReporte.Add(new General { codigo = Constantes.REPORTE_VENTAXFECHA, descripcion = Constantes.REPORTE_DESCRIPCION_VENTAXFECHA });
                listaReporte.Add(new General { codigo = Constantes.REPORTE_VENTAXPRODUCTO, descripcion = Constantes.REPORTE_DESCRIPCION_VENTAXPRODUCTO });
                listaReporte.Add(new General { codigo = Constantes.REPORTE_VENTAXCLIENTE, descripcion = Constantes.REPORTE_DESCRIPCION_VENTAXCLIENTE });
                listaReporte.Add(new General { codigo = Constantes.REPORTE_VENTAXDECORADOR, descripcion = Constantes.REPORTE_DESCRIPCION_VENTAXDECORADOR });

                //poblando lista de reportes
                this.cboReportes.DataSource = listaReporte;
                this.cboReportes.ValueMember = Constantes.GENERAL_CODIGO;
                this.cboReportes.DisplayMember = Constantes.GENERAL_DESCRIPCION;
                this.cboReportes.SelectedIndex = 0;

                // Instanciando y creando listado de documentos
                listaTipoDocumento = new ListaGeneral();
                listaTipoDocumento.Add(new General { codigo = Constantes.CODIGO_TIPO_DOCUMENTO_DNI, descripcion = Constantes.DESCRIPCION_TIPO_DOCUMENTO_DNI });
                listaTipoDocumento.Add(new General { codigo = Constantes.CODIGO_TIPO_DOCUMENTO_RUC, descripcion = Constantes.DESCRIPCION_TIPO_DOCUMENTO_RUC });
                listaTipoDocumento.Add(new General { codigo = Constantes.CODIGO_TIPO_DOCUMENTO_CE, descripcion = Constantes.DESCRIPCION_TIPO_DOCUMENTO_CE });
                listaTipoDocumento.Add(new General { codigo = Constantes.CODIGO_TIPO_DOCUMENTO_CI, descripcion = Constantes.DESCRIPCION_TIPO_DOCUMENTO_CI });

                // Estableciendo parametros del combo Tipo documento
                this.cboTipoDocumento.DataSource = listaTipoDocumento;
                this.cboTipoDocumento.ValueMember = Constantes.GENERAL_CODIGO;
                this.cboTipoDocumento.DisplayMember = Constantes.GENERAL_DESCRIPCION;
                this.cboTipoDocumento.SelectedIndex = 0;


            }
            catch (Exception ex)
            {
                log.Error(ex.Message, ex);
                Libreria.MensajeError(ex, TITULO);
            }
            finally
            {
                Cursor.Current = Cursors.Default;
            }
        }

        private void elegirTienda()
        {
            using (frmMantTienda frmMantTienda = new frmMantTienda())
            {
                frmMantTienda.formularioBusqueda = true;
                if (frmMantTienda.ShowDialog() == DialogResult.Cancel) { return; }

                this.tiendaReporte = frmMantTienda.tiendaActual;
                this.txtTiendaOCodigo.Text = this.tiendaReporte.codigo;
                this.txtTiendaODescripcion.Text = this.tiendaReporte.nombre;
            }
        }

        private void elegirProducto()
        {
            using (frmMantProducto frmMantProducto = new frmMantProducto())
            {
                frmMantProducto.formularioBusqueda = true;
                if (frmMantProducto.ShowDialog() == DialogResult.Cancel) { return; }

                this.productoReporte = frmMantProducto.productoActual;

                // Cargar datos del producto
                obtenerProductoDetalle();
            }
        }

        private void elegirCliente()
        {
            using (frmMantCliente frmMantCliente = new frmMantCliente())
            {
                frmMantCliente.formularioBusqueda = true;
                if (frmMantCliente.ShowDialog() == DialogResult.Cancel) { return; }

                this.clienteReporte = frmMantCliente.clienteActual;
                this.cboTipoDocumento.Text = this.clienteReporte.tipoDocumento;
                this.txtClienteNroDocumento.Text = this.clienteReporte.nroDocumento;
                this.txtClienteRazonSocial.Text = this.clienteReporte.razonSocial;
            }

        }

        private void elegirDecorador()
        {
            using (frmMantDecorador frmMantDecorador = new frmMantDecorador())
            {
                frmMantDecorador.formularioBusqueda = true;
                if (frmMantDecorador.ShowDialog() == DialogResult.Cancel) { return; }

                this.diseniadorReporte = frmMantDecorador.diseniadorActual;
                this.txtDecoradorCodigo.Text = this.diseniadorReporte.codDiseniador;
                this.txtDecoradorDescripcion.Text = this.diseniadorReporte.nombresyApellidos;
            }
        }

        private void obtenerProductoDetalle()
        {
            Operacion operacion = null;
            string contenidoXML = string.Empty;

            try
            {
                // Estableciendo operacion a ser enviada al Servicio REST
                operacion = new Operacion();
                operacion.numero = Constantes.OPERACION_OBTENER_PRODUCTO;
                operacion.producto = new Producto { codigo = this.productoReporte.codigo };
                operacion.tienda = new Tienda();
                operacion.tienda = ParametrosAplicacion.TIENDA_ACTUAL;

                // Instanciando y ejecutando llamada al ServicioREST
                ConexionREST conexionREST = new ConexionREST();
                contenidoXML = conexionREST.ejecutarOperacion(operacion);

                // Obteniendo Objeto de Error
                OperacionError operacionError = contenidoXML.DeserializarTo<OperacionError>();

                // Validar si hay error
                if (operacionError != null)
                {
                    Libreria.ShowMessageboxError(operacionError.descripcion);
                    return;
                }

                // Obteniendo Objeto de Producto
                Producto producto = contenidoXML.DeserializarTo<Producto>();
                productoReporte = producto;

                // Mostrar los datos del producto
                this.txtProductoCodigo.Text = producto.codigo;
                this.txtProductoDescripcion.Text = string.Format(FORMATO_PRODUCTO_DESCRIPCION_DETALLADA, producto.nivelProducto.descripcion,
                                                                                                         producto.nivelTipo.descripcion,
                                                                                                         producto.nivelMaterial.descripcion,
                                                                                                         producto.nivelColor.descripcion);

            }
            catch (Exception ex)
            {
                log.Error(ex.Message, ex);
                Libreria.MensajeError(ex, TITULO);
            }
        }

        private void limpiarDatosCliente()
        {
            // Limpiando datos del cliente anterior
            this.txtClienteRazonSocial.Text = string.Empty;
        }

        private void salir()
        {
            this.Close();
        }

        private void ejecutarReporte()
        {
            switch (this.cboReportes.SelectedValue.ToString())
            {
                case Constantes.REPORTE_VENTAXFECHA:
                    obtieneReporteVtaxFecha();
                    break;
                case Constantes.REPORTE_VENTAXCLIENTE:
                    obtieneReporteVtaxCliente();
                    break;
                case Constantes.REPORTE_VENTAXDECORADOR:
                    obtieneReporteVtaxDecorador();
                    break;
                case Constantes.REPORTE_VENTAXPRODUCTO:
                    obtieneReporteVtaxProducto();
                    break;
                default:
                    break;
            }
        }

        private void obtieneReporteVtaxCliente()
        {

            Operacion operacion = null;
            string contenidoXML = string.Empty;

            // Estableciendo operacion a ser enviada al Servicio REST
            operacion = new Operacion();
            operacion.numero = Constantes.OPERACION_OBTENER_REPORTE_VENTAXCLIENTE; /*Cambiar la constante sesún corresponda el item del comboc de la consulta*/

            operacion.reporteSolicitud = new ReporteSolicitud(); /*Se llamaría a reporteInventario*/
            operacion.reporteSolicitud.fechaInicio = this.dtpFechaInicio.Value.ToString(Constantes.FORMATO_FECHAHORA); /*Ya no va*/
            operacion.reporteSolicitud.fechaFin = this.dtpFechaFin.Value.ToString(Constantes.FORMATO_FECHAHORA); /*Ya no va*/

            operacion.reporteSolicitud. cliente = new Cliente(); /*Se debería instanciar un objeto de la clase inventario: operacion.reporteInventario.inventario.Tienda = new Tienda();*/
            operacion.reporteSolicitud.cliente = this.clienteReporte; /*Arriba definir algo asi: Private Tienda tiendaInventario*/

            // Instanciando y ejecutando llamada al ServicioREST
            ConexionREST conexionREST = new ConexionREST();
            contenidoXML = conexionREST.ejecutarOperacion(operacion);

            // Obteniendo Objeto de Error
            OperacionError operacionError = contenidoXML.DeserializarTo<OperacionError>();

            // Validar si hay error
            if (operacionError != null)
            {
                Libreria.ShowMessageboxError(operacionError.descripcion);
                return;
            }

            // Obteniendo Objeto de ReporteVenta
            this.reporteVenta = contenidoXML.DeserializarTo<ReporteVenta>(); /*<Reporteinventario>*/

            //poblar la grilla
            poblarGrilla();
        }

        private void obtieneReporteVtaxFecha()
        {

            Operacion operacion = null;
            string contenidoXML = string.Empty;

            // Estableciendo operacion a ser enviada al Servicio REST
            operacion = new Operacion();
            operacion.numero = Constantes.OPERACION_OBTENER_REPORTE_VENTAXFECHA;

            operacion.reporteSolicitud = new ReporteSolicitud();
            operacion.reporteSolicitud.fechaInicio = this.dtpFechaInicio.Value.ToString(Constantes.FORMATO_FECHAHORA);
            operacion.reporteSolicitud.fechaFin = this.dtpFechaFin.Value.ToString(Constantes.FORMATO_FECHAHORA);

            // Instanciando y ejecutando llamada al ServicioREST
            ConexionREST conexionREST = new ConexionREST();
            contenidoXML = conexionREST.ejecutarOperacion(operacion);

            // Obteniendo Objeto de Error
            OperacionError operacionError = contenidoXML.DeserializarTo<OperacionError>();

            // Validar si hay error
            if (operacionError != null)
            {
                Libreria.ShowMessageboxError(operacionError.descripcion);
                return;
            }

            // Obteniendo Objeto de ReporteVenta
            this.reporteVenta = contenidoXML.DeserializarTo<ReporteVenta>();

            //poblar la grilla
            poblarGrilla();
        }

        private void obtieneReporteVtaxProducto()
        {

            Operacion operacion = null;
            string contenidoXML = string.Empty;

            // Estableciendo operacion a ser enviada al Servicio REST
            operacion = new Operacion();
            operacion.numero = Constantes.OPERACION_OBTENER_REPORTE_VENTAXPRODUCTO;

            operacion.reporteSolicitud = new ReporteSolicitud();
            operacion.reporteSolicitud.fechaInicio = this.dtpFechaInicio.Value.ToString(Constantes.FORMATO_FECHAHORA);
            operacion.reporteSolicitud.fechaFin = this.dtpFechaFin.Value.ToString(Constantes.FORMATO_FECHAHORA);

            operacion.reporteSolicitud.producto = new Producto();
            operacion.reporteSolicitud.producto = this.productoReporte;

            // Instanciando y ejecutando llamada al ServicioREST
            ConexionREST conexionREST = new ConexionREST();
            contenidoXML = conexionREST.ejecutarOperacion(operacion);

            // Obteniendo Objeto de Error
            OperacionError operacionError = contenidoXML.DeserializarTo<OperacionError>();

            // Validar si hay error
            if (operacionError != null)
            {
                Libreria.ShowMessageboxError(operacionError.descripcion);
                return;
            }

            // Obteniendo Objeto de ReporteVenta
            this.reporteVenta = contenidoXML.DeserializarTo<ReporteVenta>();

            //poblar la grilla
            poblarGrilla();
        }

        private void obtieneReporteVtaxDecorador()
        {

            Operacion operacion = null;
            string contenidoXML = string.Empty;

            // Estableciendo operacion a ser enviada al Servicio REST
            operacion = new Operacion();
            operacion.numero = Constantes.OPERACION_OBTENER_REPORTE_VENTAXDECORADOR;

            operacion.reporteSolicitud = new ReporteSolicitud();
            operacion.reporteSolicitud.fechaInicio = this.dtpFechaInicio.Value.ToString(Constantes.FORMATO_FECHAHORA);
            operacion.reporteSolicitud.fechaFin = this.dtpFechaFin.Value.ToString(Constantes.FORMATO_FECHAHORA);

            operacion.reporteSolicitud.diseniador = new Diseniador();
            operacion.reporteSolicitud.diseniador = this.diseniadorReporte;

            // Instanciando y ejecutando llamada al ServicioREST
            ConexionREST conexionREST = new ConexionREST();
            contenidoXML = conexionREST.ejecutarOperacion(operacion);

            // Obteniendo Objeto de Error
            OperacionError operacionError = contenidoXML.DeserializarTo<OperacionError>();

            // Validar si hay error
            if (operacionError != null)
            {
                Libreria.ShowMessageboxError(operacionError.descripcion);
                return;
            }

            // Obteniendo Objeto de ReporteVenta
            this.reporteVenta = contenidoXML.DeserializarTo<ReporteVenta>();

            //poblar la grilla
            poblarGrilla();
        }

        private void poblarGrilla()
        {
        ListaLineaReporteVenta nuevaListaLineaReporteVenta = new ListaLineaReporteVenta(); /*llamar a ListaLineaReporteInventario*/

            this.dgvListado.AutoGenerateColumns = false;

            if (this.txtTiendaOCodigo.Text != "")
            {
                foreach (LineaReporteVenta lineaReporteVentaActual in reporteVenta.listaLineaReporteVenta.lista)
                {
                    if (lineaReporteVentaActual.venta.tienda.codigo == txtTiendaOCodigo.Text) /*Ver el nombre de la variable de la caja de texto del código del inventario*/
                    {
                        nuevaListaLineaReporteVenta.add(lineaReporteVentaActual);
                    }
                }

                this.dgvListado.DataSource = nuevaListaLineaReporteVenta == null ?
                                                     new ListPersonalizada<LineaReporteVenta>() :
                                                     nuevaListaLineaReporteVenta.lista;


            }
            else
            {
                this.dgvListado.DataSource = reporteVenta.listaLineaReporteVenta == null ?
                                                      new ListPersonalizada<LineaReporteVenta>() :
                                                      reporteVenta.listaLineaReporteVenta.lista;


            }

            pintarGrilla(this.dgvListado);

        }

        private void pintarGrilla(DataGridView grilla)
        {
            ListPersonalizada<LineaReporteVenta> listaLineaReporteVenta = null;
            listaLineaReporteVenta = (ListPersonalizada<LineaReporteVenta>)grilla.DataSource;

            if (listaLineaReporteVenta != null)
            {
                for (int i = 0; i < listaLineaReporteVenta.Count; i++)
                {
                    LineaReporteVenta lineaReporteVenta = listaLineaReporteVenta[i];
                    this.dgvListado.Rows[i].Cells[0].Value = lineaReporteVenta.venta.tipoDocumentoVenta.descripcion;
                    this.dgvListado.Rows[i].Cells[1].Value = lineaReporteVenta.venta.serie;
                    this.dgvListado.Rows[i].Cells[2].Value = lineaReporteVenta.venta.numero;
                    this.dgvListado.Rows[i].Cells[3].Value = lineaReporteVenta.venta.cliente.razonSocial;
                    this.dgvListado.Rows[i].Cells[4].Value = lineaReporteVenta.venta.diseniador.nombresyApellidos;
                    this.dgvListado.Rows[i].Cells[5].Value = lineaReporteVenta.venta.usuario.nombres + " " + lineaReporteVenta.venta.usuario.apellidos;
                    this.dgvListado.Rows[i].Cells[6].Value = lineaReporteVenta.descripcionEstado;
                    this.dgvListado.Rows[i].Cells[7].Value = lineaReporteVenta.venta.subTotal.ToString();
                    this.dgvListado.Rows[i].Cells[8].Value = lineaReporteVenta.venta.igv.ToString();
                    this.dgvListado.Rows[i].Cells[9].Value = lineaReporteVenta.venta.total.ToString();
                }
            }
        }

        private void exportarData()
        {
            if (this.dgvListado.DataSource == null)
            {
                ejecutarReporte();
            }

            ExportarExcel exportarExcel = null;

            try
            {
                // Si no hay informacion en la grilla entoncesa salir
                if (this.dgvListado.Rows.Count <= 0) { return; }

                // Si hay informacion entonces generar archivo
                exportarExcel = new ExportarExcel();
                String sNombreArchivo = "";
                switch (this.cboReportes.SelectedValue.ToString())
                {
                    case Constantes.REPORTE_VENTAXFECHA:
                        sNombreArchivo = RUTA_ARCHIVO_TEMPORAL + "\\REPORTE_VENTAXFECHA." + DateTime.Now.ToString(Constantes.FORMATO_FECHAHORA_ARCHIVO) + ".xls";
                        break;
                    case Constantes.REPORTE_VENTAXCLIENTE:
                        sNombreArchivo = RUTA_ARCHIVO_TEMPORAL + "\\REPORTE_VENTAXCLIENTE." + DateTime.Now.ToString(Constantes.FORMATO_FECHAHORA_ARCHIVO) + ".xls";
                        break;
                    case Constantes.REPORTE_VENTAXDECORADOR:
                        sNombreArchivo = RUTA_ARCHIVO_TEMPORAL + "\\REPORTE_VENTAXDECORADOR." + DateTime.Now.ToString(Constantes.FORMATO_FECHAHORA_ARCHIVO) + ".xls";
                        break;
                    case Constantes.REPORTE_VENTAXPRODUCTO:
                        sNombreArchivo = RUTA_ARCHIVO_TEMPORAL + "\\REPORTE_VENTAXPRODUCTO." + DateTime.Now.ToString(Constantes.FORMATO_FECHAHORA_ARCHIVO) + ".xls";
                        break;
                    default:
                        break;
                }

                exportarExcel.crearExcelTabla(sNombreArchivo, this.dgvListado);

                // Abrir archivo generado
                ProcessStartInfo psi = new ProcessStartInfo(APLICACION_EXCEL, RUTA_ARCHIVO_TEMPORAL);
                Process p = Process.Start(psi);
            }
            catch (Exception ex)
            {
                log.Error(ex.Message, ex);
                Libreria.MensajeError(ex, this.Text);
            }
        }
        #endregion
    }
}
